package com.chuanke.ckfamily.service.user.thread;

import java.sql.Timestamp;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.chuanke.ckfamily.dao.finance.model.Bill;
import com.chuanke.ckfamily.service.common.CacheService;
import com.chuanke.ckfamily.service.common.impl.RedisLockUtil;
import com.chuanke.ckfamily.service.constant.BillStatus;
import com.chuanke.ckfamily.service.finance.BillService;
import com.chuanke.ckfamily.service.util.CkServerUtil;

/**
 * Created by xiaoxia on 2017/8/22.
 */
public class UploadUserMoneyThread extends Thread {

    private Logger logger = LoggerFactory.getLogger(UploadUserMoneyThread.class);

    // 线程启动标识
    private boolean begin;

    private long sleepTime = 10000L;

    protected CacheService cacheService;

    protected BillService billService;

    private static final String REDIS_KEY = "UploadUserMoney_CountThread";

    public UploadUserMoneyThread(CacheService cacheService,BillService billService){
        this.cacheService = cacheService;
        this.billService = billService;
    }

    public void start(){
        this.begin = true;
        super.start();
    }
    @Override
    public void run() {
        while(begin){
            Long span = 0l;
            while (begin) {
                span = System.currentTimeMillis() - getTime();
                if (span >= 2 * sleepTime) {
                    setTime();
                    break;
                }

                threadSleep(2 * sleepTime);
            }

            while (span >= sleepTime) {
                long start = System.currentTimeMillis();
                setTime();

                try {
                    execute();
                } catch (Exception e) {
                    e.printStackTrace();
                }

                threadSleep(sleepTime - (System.currentTimeMillis() - start - 200));
                span = System.currentTimeMillis() - getTime();
            }

        }
    }

    // 执行的业务逻辑
    public void execute(){
        Long size = cacheService.listSize(CacheService.KEY_PREFIX.bill_queue.name());
        if (size == null || size == 0) {
            return;
        }

        Bill bill = null;
        do {
            try {
                bill = (Bill)cacheService.rightPop(CacheService.KEY_PREFIX.bill_queue.name());
                if (bill != null) {
                    boolean isSuccess = CkServerUtil.uploadUserMoney(bill, cacheService);
                    if(isSuccess){
                        bill.setFlag(BillStatus.SUBMITED.getStatus());//  设置为1表示成功上传
                    } else {
                        bill.setFlag(BillStatus.FAIL.getStatus());
                    }

                    bill.setUpdate_time(new Timestamp(System.currentTimeMillis()));
                    this.billService.update(bill);

                    sleep(50);
                }

            } catch (Exception e) {
                e.printStackTrace();

            }

        } while (bill != null);

    }

    protected void threadSleep(long time) {
        synchronized (this) {
            try {
                if (time < 10) {
                    time = 10;
                }
                sleep(time);

            } catch (Exception e) {
                e.printStackTrace();
                try {
                    sleep(10);
                } catch (InterruptedException e1) {
                    e1.printStackTrace();
                }

            }
        }
    }

    private void setTime() {
        RedisLockUtil lock = null;
        try {
            lock = cacheService.getLock(REDIS_KEY);
            cacheService.set(REDIS_KEY, System.currentTimeMillis());

        } catch (Exception e) {
            e.printStackTrace();

        } finally {
            if (lock != null) {
                lock.unlock();
            }

        }
    }

    private Long getTime() {
        Long time = (Long) cacheService.get(REDIS_KEY);
        if (time == null) {
            time = 0l;
        }

        return time;
    }
}
